home *** CD-ROM | disk | FTP | other *** search
/ BMUG Revelations / BMUG Revelations.toast / Programming / Programming Languages / Yerk 3.64 / Supplement / Unsupported / Optionals / Print Drvr < prev    next >
Text File  |  1986-09-19  |  11KB  |  354 lines

  1. \
  2. \ Printer glue routines
  3. \ See Inside MacIntosh for more information on their use
  4. \
  5. \ NOTE: Because of some bugs in the NEON Assembler some awkward code was used
  6. \  1:  the first 2 lines of PRERROR should be "MOVE.W $0944,D0"
  7. \      but the assembler can not handle absolute addresses
  8. \  2:  Extra NOPs are in some words because branch addresses are calculated
  9. \      wrong when toolbox calls are used in the same word.  
  10. \
  11.  
  12. SCON PRNAME ".Print"    \ name of printer driver
  13.  
  14. \
  15. \ This routine returns the value of the printer error global
  16. \ ( -- error )
  17. :CODE PrError
  18.     MOVEA.W #$0944,A0   \ load address of global
  19.     MOVE.W  (A0),D0     \ get value
  20.     EXT.L   D0          \ make it NEON full word
  21.     MOVE.L  D0,-(A7)    \ stack it
  22. ;CODE
  23.  
  24. \
  25. \ This routine sets the value of the printer error global
  26. \ ( error -- )
  27. :CODE PrSetError
  28.     MOVE.L  (A7)+,D0    \ Un-stack value
  29.     MOVEA.W #$0944,A0   \ load address of global
  30.     MOVE.W  D0,(A0)     \ set value
  31. ;CODE
  32.  
  33. \
  34. \ this routine is assembler callable only.  It opens the printer driver
  35. \
  36. :CODE (PrDrvrOpen)
  37.     MOVEQ   #24,D0      \ clear a parameter block on the stack
  38. L1  CLR.W   -(A7)
  39.     DBF     D0,L1
  40.     MOVE.L  NEON[prname],A0 \ get NEON address of SCON
  41.     ADD.L   #4,A0       \ advance past 1cfa
  42.     ADDA.L  A3,A0       \ +base
  43.     MOVE.L  A0,18(A7)   \ move into parameter block
  44.     MOVE.L  A7,A0
  45.     Call    Open        \ open printer driver
  46.     ADDA.W  #50,A7      \ clear parameter block from stack
  47.     MOVEA.W #$0944,A0   \ load address of printer global
  48.     MOVE.W  D0,(A0)     \ set value to returned error code
  49.     RTS
  50. ;CODE
  51.  
  52. \
  53. \ the NEON callable routine to open the printer driver
  54. \ ( -- ) result in PrError
  55. :CODE PrDrvrOpen
  56.     MOVE.L  NEON[(PrDrvrOpen)],D7
  57.     JSR     0(A3,D7.l)
  58. ;CODE
  59.  
  60. \
  61. \ Routine to close the printer driver
  62. \ ( -- ) result in PrError
  63. :CODE PrDrvrClose
  64.     SUBA.W  #50,A7      \ clear a parameter block on the stack
  65.     MOVE.L  A7,A0
  66.     MOVE.W  #-3,24(A0)  \ move in device number of printer driver
  67.     Call    Close       \ close driver
  68.     ADDA.W  #50,A7      \ clear parameter block from stack
  69.     MOVEA.W #$0944,A0  \ load address of printer global
  70.     MOVE.W  D0,(A0)     \ set value
  71. ;CODE
  72.  
  73. \
  74. \ This routine is assembler callable only.
  75. \ It gets the string resource containing the file name that the CHOOSER
  76. \ has placed in the file SYSTEM.  This file is then opened as a resource file.
  77. \ On return, Prerror contains the result code.
  78. \ If PrError = 0 then D0 contains the reference number from OpenResFile.
  79. \ ( -- ) result in PrError
  80. :CODE (PrOpen)
  81.     SUBQ    #4,A7       \ make room for a handle
  82.     MOVE.L  #$53545220,-(A7)  \ push 'TYPE STRb
  83.     MOVE.W  #$-2000,-(A7) \ push resource number ($E000) of printer file name
  84.     Call    GetResource
  85.     MOVE.L  (A7)+,D0    \ pop resource handle
  86.     BEQ     ERR         \ if NIL, return error in PrError
  87.     MOVE.L  D0,A1
  88.     SUBQ    #2,A7       \ make room on stack for result of open
  89.     MOVE.L  (A1),-(A7)  \ push address of string
  90.     BSET.B  #7,(A1)     \ lock string resource
  91.     Call    OpenResFile \ try to open resource file
  92.     MOVE.W  (A7)+,D0    \ pop result code
  93.     BCLR.B  #7,(A1)     \ unlock string resource (its purgeable!)
  94.     MOVEA.W #2656,A0    \ load address ($0A60) of ResErr global
  95.     MOVEA.W #$0944,A1   \ load address of PrintErr global
  96.     MOVE.W  (A0),(A1)   \ copy ResErr to PrintErr
  97.     RTS
  98. ERR NOP                 \ NOPs are to bypass the NEON assembler bug
  99.     NOP
  100.     MOVEA.W #$0944,A1
  101.     MOVE.W  #-192,(A1)  \ set error into printer global
  102.     RTS
  103. ;CODE
  104.  
  105. \
  106. \ This routine opens the printer driver and the print resource file
  107. \ in preparation for printing
  108. \ ( -- ) result in PrError
  109. :CODE PrOpen
  110.     MOVE.L  NEON[(PrDrvrOpen)],D7
  111.     JSR     0(A3,D7.l)  \ go open the printer driver
  112.     MOVEA.W #$0944,A0
  113.     TST.W   (A0)        \ check if it worked
  114.     BNE     DONE
  115.     MOVE.L  NEON[(PrOpen)],D7
  116.     JSR     0(A3,D7.l)  \ go open the printer resource file
  117. DONE NOP
  118. ;CODE
  119.  
  120. \
  121. \ This routine closes the printer resource file by first opening it
  122. \ just to get the reference number, and then closing it.
  123. \ ( -- ) result in PrError
  124. :CODE PrClose
  125.     MOVE.L  NEON[(PrOpen)],D7
  126.     JSR     0(A3,D7.l)  \ go open the printer driver, D0 = file reference
  127.     MOVEA.W  #$0944,A0  \ load address of PrintErr global
  128.     TST.W   (A0)        \ check it
  129.     BNE     DONE
  130.     MOVE.W  D0,-(A7)    \ push resource file reference number
  131.     Call    ClosResFile
  132.     MOVEA.W #2656,A0    \ load address ($0A60) of ResErr global
  133.     MOVEA.W #$0944,A1   \ load address of PrintErr global
  134.     MOVE.W  (A0),(A1)   \ copy ResErr to PrintErr
  135. DONE NOP
  136. ;CODE
  137.  
  138. \
  139. \ This routine does a control call to the printer driver.
  140. \ See Inside MacIntosh for more information.
  141. \ ( iWhichCtl lParam1 lParam2 lParam3 -- )
  142. :CODE PrCtlCall
  143.     MOVE.L  (A7)+,A1    \ pop lParam3
  144.     MOVE.L  (A7)+,D0    \ pop lParam2
  145.     MOVE.L  (A7)+,D1    \ pop lParam1
  146.     MOVE.L  (A7)+,D2    \ pop iWhichCtl
  147.     SUBA.W  #50,A7      \ make parameter block on stack
  148.     MOVE.W  D2,26(A7)   \ move in parameters
  149.     MOVE.L  D1,28(A7)
  150.     MOVE.L  D0,32(A7)
  151.     MOVE.L  A1,36(A7)
  152.     MOVE.W  #-3,24(A7)  \ driver number = -3
  153.     MOVE.L  A7,A0
  154.     Call    Control
  155.     ADDA.W  #50,A7      \ remove parameter block from stack
  156.     MOVEA.W #$0944,A0   \ load address of PrintErr global
  157.     MOVE.W  D0,(A0)     \ copy error code to it
  158. ;CODE
  159.  
  160. \
  161. \ This routine is used to call an appropriate printer routine.
  162. \ Printer routines are contained in PDEF resources that are actually
  163. \ code resources with a jump table at the beginning.
  164. \ This routine is called with a variable number of parameters, the PDEF
  165. \ resource number and a control word.
  166. \ The high order 16 bits of the control word contains number of bytes to pop
  167. \ from the stack if the code resource can not be loaded.  The high order bit
  168. \ of the next 16 bits is on if the PDEF resource should not be unlocked
  169. \ after it is called.  The lowest 8 bits of the control word contain the
  170. \ jump table offset of the appropriate routine to call in the PDEF resource.
  171. \ e.g. 5 $ 00148000 PrintGlue calls PrPicFile
  172. :CODE PrintGlue
  173.     MOVE.L  A4,-(A6)            \ save NEON Instruction Ptr on return stack
  174.     MOVE.L  (A7)+,D4            \ pop control word
  175.     MOVE.L  (A7)+,D0            \ pop segment number
  176.     SUBQ.L  #4,A7               \ make room on stack
  177.     MOVE.L  #$50444546,-(A7)    \ push 'TYPE PDEF
  178.     MOVE.W  D0,-(A7)            \ push resource (i.e. segment) number
  179.     Call    GetResource         \ get printer code segment
  180.     MOVE.L  (A7)+,D0            \ pop resource handle
  181.     BEQ     ERR                 \ if zero, get failed
  182.     MOVE.L  D0,A4
  183.     BSET    #7,(A4)             \ lock segment
  184.     MOVE.L  (A4),A0             \ get code segment address
  185.     MOVEQ   #0,D0
  186.     MOVE.B  D4,D0
  187.     ADDA.L  D0,A0               \ calculate jump table address
  188.     MOVE.L  A0,-(A7)
  189.     CLR.B   (A7)                \ clear high order byte of routine address
  190.     MOVE.L  (A7)+,A0
  191.     JSR     (A0)                \ call print routine
  192.     TST.W   D4                  \ MSB of word: on implies unlock needed
  193.     BPL     OUT
  194.     BCLR    #7,(A4)             \ unlock segment
  195.     BRA     OUT
  196. ERR NOP                         \ NOP for NEON Assembler branch error
  197.     MOVEA.W #$0944,A0           \ load address of PrintErr global
  198.     MOVE.W  #-192,(A0)          \ set error
  199.     SWAP    D4                  \ clean up stack, as GetResource failed
  200.     ADDA.W  D4,A7
  201. OUT NOP                         \ NOP for NEON Assembler branch error
  202.     MOVE.L  (A6)+,A4            \ pop NEON Instruction Ptr from return stack
  203. ;CODE
  204.  
  205. endASM
  206.  
  207. : (PrintMethod) ( -- code segment number of current printing method )
  208.   $ 0946 -base c@ 3 and
  209. ;
  210.  
  211. \ This routine opens the document for printing
  212. \ We will supply the printing grafport, so that it can be a NEON Object
  213. : PrOpenDoc    { THPrint -- tpprport }
  214.     \ the following moves the low order 3 bits of THPrint.bJDocLoop
  215.     \ to printer global $ 0946
  216.     \ these bits contain the code segment number that represents
  217.     \ the printing method chosen (e.g. draft vs. spool )
  218.     $ 0946 -base dup c@         \ get another printer global
  219.     $ FC and                    \ clear lower 3 bits
  220.     ptr: THPrint 68 + c@ 3 and  \ get masked printing method
  221.     or                          \ or in other bits from printer global
  222.     swap c!                     \ stash it back in global
  223.     0             ( for returned port address )
  224.     get: THPrint  ( the print record )
  225.     0             ( we will supply the printing grafport )
  226.     0             ( NIL buffer address )
  227.     (PrintMethod) $ 000C0000 PrintGlue
  228. ;
  229.  
  230. : PrCloseDoc   { TPPrPort -- }
  231.     TPPrPort
  232.     (PrintMethod) $ 00048004 PrintGlue
  233. ;
  234.  
  235. : PrOpenPage   { TPPrPort TPRect -- }
  236.     TPPrPort
  237.     TPRect 0= IF 0 ELSE abs: TPRect THEN \ page scaling rectangle, if not NIL
  238.     (PrintMethod) $ 00040008 PrintGlue
  239. ;
  240.  
  241. : PrClosePage  { TPPrPort -- }
  242.     TPPrPort
  243.     (PrintMethod)  $ 0004000C PrintGlue
  244. ;
  245.  
  246. : PrCFGDialog
  247.     6 $ 00008000 PrintGlue
  248. ;
  249.  
  250. : PrintDefault { THPrint -- }
  251.     get: THPrint 4 $ 00048000 PrintGlue
  252. ;
  253.  
  254. : PrStlDialog  { THPrint -- true or false }
  255.     word0 get: THPrint
  256.     4 $ 00048004 PrintGlue word0 not not
  257. ;
  258.  
  259. : PrJobDialog  { THPrint -- true or false }
  260.     word0 get: THPrint
  261.     4 $ 00048008 PrintGlue word0 not not
  262. ;
  263.  
  264. : PrStlInit    { THPrint -- TPPrDlg }
  265.     0  get: THPrint
  266.     4 $ 0004000C PrintGlue
  267. ;
  268.  
  269. : PrJobInit    { THPrint -- TPPrDlg }
  270.     0  get: THPrint
  271.     4 $ 00040010 PrintGlue
  272. ;
  273.  
  274. : PrDlgMain    { THPrint DlgProc -- true or false }
  275.     word0 get: THPrint DlgProc
  276.     4 $ 00088014 PrintGlue word0 not not
  277. ;
  278.  
  279. : PrValidate   { THPrint -- true or false }
  280.     word0 get: THPrint
  281.     4 $ 00048018 PrintGlue word0 not not
  282. ;
  283.  
  284. : PrJobMerge   { THPrint -- true or false }
  285.     word0 get: THPrint
  286.     4 $ 0008801C PrintGlue word0 not not
  287. ;
  288.  
  289. : PrPicFile    { THPrint TPrStatus -- }
  290.     get: THPrint
  291.     0 ( port address )  0 ( I/O buffer )  0 ( device buffer )
  292.     abs: TPrStatus ( print status record )
  293.     5 $ 00148000 PrintGlue
  294. ;
  295.  
  296. \
  297. \ Printing Status record
  298. \ Methods can be added later
  299. \
  300. :CLASS TPrStatus <super Object
  301.     int    TotPages     \ number of pages in spool file
  302.     int    CurPage      \ page being printed
  303.     int    TotCopies    \ number of copies requested
  304.     int    CurCopy      \ copy being printed
  305.     int    TotBands
  306.     int    CurBand
  307.   1 bytes  PgDirty      \ true if started printing page
  308.   1 bytes  Imaging
  309.     handle hPrint       \ print record
  310.     var    pPrPort      \ printing grafport
  311.     handle hPic
  312. ;CLASS
  313.  
  314. \
  315. \ a test of the printer routines
  316. \
  317. handle    hPrint
  318. TPrStatus theStatus
  319. 0 value   PrPort
  320. rect      rtest
  321. : PrintTest
  322.   PrOpen
  323.   PrError 0= 
  324.   IF
  325.     200 new: hPrint
  326.     hPrint PrintDefault
  327.     hPrint PrValidate  drop
  328.     hPrint PrStlDialog drop
  329.     hPrint PrJobDialog
  330.     IF
  331.       pushport
  332.       hPrint PrOpenDoc -> PrPort
  333.       PrError 0=
  334.       IF
  335.         PrPort 0 PrOpenPage
  336.         PrError 0=
  337.         IF
  338.           example: rtest 20 10 inset: rtest draw: rtest
  339.         THEN
  340.         PrPort PrClosePage
  341.       THEN
  342.       PrPort PrCloseDoc
  343.       PrError 0=   ptr: hPrint 68 + c@ 1 =  and
  344.       IF
  345.         hPrint theStatus PrPicFile
  346.       THEN
  347.       popport
  348.     THEN
  349.     release: hPrint
  350.   THEN
  351.   PrClose
  352. ;
  353.  
  354.